<template>
	<view class="chat-page">
		<scroll-view
			class="chat-scroll"
			scroll-y
			:scroll-into-view="intoViewId"
			:scroll-with-animation="false"
			@scroll="handleScroll"
			@scrolltolower="loadNewMessages"
			ref="scrollViewRef">
			<view v-for="item in messages" :key="item.id" :id="item.id" class="message-item">
				<view class="sticky-title">{{ item.text }}</view>
				<view v-for="item in item.children" :key="item.id" class="goods-item" style="padding: 30px 0;">
					{{ item.text }}
				</view>
			</view>
		</scroll-view>
	</view>
</template>

<script setup>
	import { ref, onMounted, nextTick } from 'vue'

	const messages = ref([])
	const intoViewId = ref('')
	const PAGE_SIZE = 3
	let isLoadingTop = false
	let isLoadingBottom = false

	const scrollViewRef = ref(null)

	// 模拟接口
	function fetchMessages({ direction }) {
		return new Promise(resolve => {
			setTimeout(() => {
				const list = Array.from({ length: PAGE_SIZE }, (_, i) => ({
					id: `${direction}-${Date.now()}-${i}`,
					text: `${
						direction === 'init' ? '中间消息' : direction === 'up' ? '旧消息' : '新消息'
					} ${i + 1}`,
					children: Array.from({ length: 20 }, (_, ai) => ({
						id: `${direction}-${Date.now()}-${ai}`,
						text: `内容`,
					})),
				}))
				resolve(list)
			}, 500)
		})
	}

	// 判断平台 (简单示例，实际可用uni.getSystemInfo或其它)
	const isWeChatMiniProgram = typeof wx !== 'undefined' && wx.getSystemInfoSync !== undefined

	// 初始化加载，滚动到中间
	onMounted(async () => {
		const data = await fetchMessages({ direction: 'init' })
		messages.value = data
		await nextTick()
		const midIndex = Math.floor(messages.value.length / 2)
		intoViewId.value = messages.value[midIndex]?.id
	})

	function handleScroll(e) {
		const top = e.detail.scrollTop
		if (top < 50 && !isLoadingTop) {
			isLoadingTop = true
			loadOldMessages()
		}
	}

	// 上拉加载旧消息，保持位置
	async function loadOldMessages() {
		const anchorId = messages.value[0]?.id
		const newMessages = await fetchMessages({ direction: 'up' })
		messages.value = [...newMessages, ...messages.value]
		await nextTick()
		intoViewId.value = anchorId
		isLoadingTop = false
	}

	// 触底加载新消息，自动滚到底部，兼容小程序和H5
	async function loadNewMessages() {
		if (isLoadingBottom) return
		isLoadingBottom = true

		const newMessages = await fetchMessages({ direction: 'down' })
		messages.value = [...messages.value, ...newMessages]
		await nextTick()

		if (isWeChatMiniProgram) {
			// 微信小程序滚动到底部写法
			uni.createSelectorQuery()
				.select('.chat-scroll')
				.boundingClientRect()
				.exec(() => {
					uni.pageScrollTo({
						scrollTop: 99999,
						duration: 0,
					})
				})
		} else {
			// H5及其他平台，直接设置scrollTop
			scrollToBottom()
		}

		isLoadingBottom = false
	}

	// H5滚动到底部函数
	function scrollToBottom() {
		setTimeout(() => {
			const el = scrollViewRef.value
			if (!el) return
			// scrollViewRef 是vue组件ref，H5下它实际是DOM
			if ('scrollTop' in el) {
				el.scrollTop = 999999
			} else if (el.$el) {
				el.$el.scrollTop = 999999
			}
		}, 10)
	}
</script>

<style scoped>
	.chat-page {
		height: 100vh;
		display: flex;
		flex-direction: column;
	}

	.chat-scroll {
		flex: 1;
		height: 100%;
		background-color: #f5f5f5;
		overflow-y: scroll;
	}

	.message-item {
		background-color: #fff;
		border-bottom: 1rpx solid #ddd;
		font-size: 28rpx;
	}

	.sticky-title {
		position: sticky;
		top: 0;
		background: #fff;
		z-index: 10;
		font-weight: bold;
		font-size: 28rpx;
		padding: 20rpx 0 10rpx;
		border-bottom: 1px solid #eee;
	}
</style>
